#!/bin/bash

arch="x86"
system="all"
current_pwd=""
package_file=""
packages=""
common_packages=""
common_depends_file=""
download_path=""
depends_download_path=""
depends="Depends"

function error() {
    local date=$(date)
    local para=$1
    echo -e "\033[31m[$date] [e] $para \033[0m"
}

function info() {
    local date=$(date)
    local para=$1
    echo -e "\033[32m[$date] [i] $para \033[0m"
}

function notify() {
    local date=$(date)
    local para=$1
    echo -e "\033[35m[$date] [n] $para \033[0m"
}

function do_get_language() {
    # 是中文
    if [[ $LANG =~ "zh_CN" ]]; then
        depends="依赖"
    fi
    # 是英文
    if [[ $LANG =~ "en_US" ]]; then
        depends="Depends"
    fi
}

function do_get_system_id() {
    source /etc/os-release
    system="$ID-$VERSION_ID"
}

function do_generate_arch() {
    # 获取arch
    arch=$(uname -m)
    if [ $arch == "x86_64" ]; then
        arch="x86"
    fi

    if [ $arch == "aarch64" ]; then
        arch="arm64"
    fi
}

function do_configure() {
    current_pwd=$(
        cd "$(dirname "$0")"
        pwd
    )

    do_get_language
    do_generate_arch
    do_get_system_id

    if [ " ${package_file}" == " " ]; then
        package_file=${current_pwd}/package.txt
    fi

    download_path=${current_pwd}/${arch}/${system}
    depends_download_path=${download_path}/depends
    common_depends_file=${depends_download_path}/common/depends.dep
    download_path=${download_path}/packages

    mkdir -p ${download_path}
    mkdir -p ${depends_download_path}
    mkdir -p ${depends_download_path}/common

    cd ${download_path}
}

function do_get_packages() {
    if [ ! -f "${package_file}" ]; then
        error "not find package : ${package_file}"
    else
        for package in $(cat $package_file); do
            packages="${packages} ${package}"
        done
        info "the following packages will be downloaded : \n$packages\n"
    fi
}

function get_depends() {
    ret=""

    # 如果不存在依赖文件，就创建
    if [ ! -f "${depends_download_path}/$1.dep" ]; then
        # use tr to del < >
        ret=$(apt-cache depends $1 | grep $depends | cut -d: -f2 | tr -d "<>")
        echo $ret >${depends_download_path}/$1.dep
    else
        ret=$(cat ${depends_download_path}/$1.dep)
    fi
    echo $ret
}

# 递归获取依赖
function get_depends_recursion() {
    i=0
    libs=$packages
    while [ $i -lt 3 ]; do
        let i++
        newlist=""
        for package in $libs; do
            info "get depends of $package ..."
            dependen="$(get_depends $package)"
            newlist="$newlist $dependen"
            newlist=$(echo $newlist | sed 's/ /\n/g' | sort -u)
        done
        libs=$newlist
    done
}

# 获取公共依赖
function get_common_depends() {
    depends_list=""
    # 读取 ${depends_download_path} 下的所有文件，组成一个依赖列表
    # for file in $(ls ${depends_download_path}); do
    #     # 如果 file 是文件
    #     if [ -f "${depends_download_path}/$file" ]; then
    #         # 如果 file 是 packages 中的包
    #         if [[ $file =~ $packages ]]; then
    #             depends_list="${depends_list} $(cat ${depends_download_path}/$file)"
    #         fi
    #     fi
    # done

    # for package in $packages; do
    #     # 如果存在 ${depends_download_path}/$package.dep 文件
    #     if [ -f "${depends_download_path}/$package.dep" ]; then
    #         tmp_package=$(cat ${depends_download_path}/$package.dep)
    #         depends_list="${depends_list} ${tmp_package}"
    #         for tmp in $tmp_package; do
    #             if [ -f "${depends_download_path}/$package.dep" ]; then
    #                 depends_list="${depends_list} $(cat ${depends_download_path}/$tmp.dep)"
    #             fi
    #         done

    #         error "find ${depends_download_path}/$package.dep"
    #         # depends_list="${depends_list} $(cat ${depends_download_path}/$package.dep)"
    #     fi
    # done

    # 提取多次出现的依赖
    common_depends=""
    for depend in $depends_list; do
        count=$(echo $depends_list | grep -o $depend | wc -l)
        if [ $count -gt 1 ]; then
            common_depends="${common_depends} ${depend}"
        fi
    done

    # 去重
    common_depends=$(echo $common_depends | sed 's/ /\n/g' | sort -u)

    # 去除换行符
    common_packages=$(echo $common_depends | tr -d "\n")

    # 写入文件
    echo $common_depends >$common_depends_file
}

# 下载公共部分的deb包
function do_download_common_packages() {
    mkdir -p ${download_path}/common
    cd ${download_path}/common

    notify "download common package : ${common_packages}\n"

    # 下载公共依赖部分的deb包
    for package in $common_packages; do
        info "download common package : ${package}"
        apt-get download $package
    done
}

function do_download_package() {
    for package in $@; do
        if [[ $common_packages =~ $package ]]; then
            # info "$package is common package"
            continue
        else
            info "download package : ${package}"
            apt-get download $package
        fi

    done
}

function do_download() {
    i=0
    libs=$1
    while [ $i -lt 3 ]; do
        let i++
        newlist=""
        for package in $libs; do
            dependen="$(get_depends $package)"
            newlist="$newlist $dependen"
            notify "start download $dependen ..."
            do_download_package $package
            do_download_package $dependen
            notify "done ...\n"
        done
        libs=$newlist
    done
}

function do_download_recursion() {
    for package in $packages; do
        mkdir -p ${download_path}/${package}
        cd ${download_path}/${package}
        do_download $package
    done
}

function do_append_packages() {
    for package in $@; do
        if [ $? -ne 0 ]; then
            error "can't download package : ${package}"
        else
            echo "${package}" >>$package_file
        fi
    done
}

function do_sort_packages() {
    sort -u $package_file >$package_file.tmp
    cp $package_file.tmp $package_file
    rm $package_file.tmp
}

main() {
    do_configure
    # do_append_packages $@
    # do_sort_packages
    # do_get_packages
    packages=$@
    get_depends_recursion
    get_common_depends
    do_download_common_packages
    do_download_recursion
}

main "$@"
